Pythonã®ãã³ã¬ãŒã¿ãŒãã¿ãŒã³ã®è©³çްã解説ãå ç¢ã§ä¿å®æ§ã®é«ãã³ãŒãã®ããã«é¢æ°ã©ããã³ã°ãšã¡ã¿ããŒã¿ä¿æãæ¯èŒããŸãããã¶ã€ã³ãã¿ãŒã³ãæ·±ãçè§£ãããã°ããŒãã«ãªéçºè ã«æé©ã§ãã
ãã³ã¬ãŒã¿ãŒãã¿ãŒã³ã®å®è£ ïŒPythonã«ããã颿°ã©ããã³ã°ãšã¡ã¿ããŒã¿ä¿æã®æ¯èŒ
ãã³ã¬ãŒã¿ãŒãã¿ãŒã³ã¯ãæ¢åã®ãªããžã§ã¯ãã颿°ã®å ã®æ§é ã倿Žããããšãªããåçã«æ°ããæ©èœã远å ã§ããã匷åã§ãšã¬ã¬ã³ããªãã¶ã€ã³ãã¿ãŒã³ã§ããPythonã§ã¯ããã³ã¬ãŒã¿ãŒã¯ãã®ãã¿ãŒã³ãéåžžã«çŽæçã«å®è£ ã§ããã·ã³ã¿ãã¯ã¹ã·ã¥ã¬ãŒã§ããããããç¹ã«Pythonããã¶ã€ã³ãã¿ãŒã³ã«äžæ £ããªéçºè ãé¥ããããèœãšã穎ã¯ãåã«é¢æ°ãã©ããããããšãšããã®å ã®ã¡ã¿ããŒã¿ãä¿æããããšã®éã®ã埮åŠãªãããæ±ºå®çãªéããçè§£ããããšã«ãããŸãã
ãã®å æ¬çãªã¬ã€ãã§ã¯ãPythonãã³ã¬ãŒã¿ãŒã®ã³ã¢ã³ã³ã»ãããæãäžããåºæ¬çãªé¢æ°ã©ããã³ã°ãšãããåªããã¡ã¿ããŒã¿ä¿æã®æ¹æ³ãšã®æç¢ºãªã¢ãããŒãã®éããæããã«ããŸããç¹ã«å ±åäœæ¥ãã°ããŒãã«ãªéçºç°å¢ã«ãããŠãå ç¢ã§ãã¹ãå¯èœããã€ä¿å®æ§ã®é«ãã³ãŒãã«ãšã£ãŠãªãã¡ã¿ããŒã¿ã®ä¿æãäžå¯æ¬ ãªã®ããæ¢ããŸãã
Pythonã«ããããã³ã¬ãŒã¿ãŒãã¿ãŒã³ã®çè§£
Pythonã«ããããã³ã¬ãŒã¿ãŒã®æ žå¿ã¯ãå¥ã®é¢æ°ãåŒæ°ãšããŠåãåããäœããã®æ©èœã远å ãããããŠå¥ã®é¢æ°ãè¿ã颿°ã§ãããã®è¿ããã颿°ã¯ãå€ãã®å Žåãå ã®é¢æ°ãä¿®æ£ãŸãã¯æ¡åŒµãããã®ã§ãããå ã®é¢æ°ãåŒã³åºãå šãæ°ãã颿°ã§ããããšããããŸãã
Pythonãã³ã¬ãŒã¿ãŒã®åºæ¬æ§é
åºæ¬çãªäŸããå§ããŸãããã颿°ããã€åŒã³åºããããããã°ã«èšé²ããããšããŸããåçŽãªãã³ã¬ãŒã¿ãŒã§ãããå®çŸã§ããŸãïŒ
def simple_logger_decorator(func):
def wrapper(*args, **kwargs):
print(f"Calling function: {func.__name__}")
result = func(*args, **kwargs)
print(f"Finished calling function: {func.__name__}")
return result
return wrapper
@simple_logger_decorator
def greet(name):
return f"Hello, {name}!"
print(greet("Alice"))
ãã®ã³ãŒããå®è¡ãããšãåºåã¯æ¬¡ã®ããã«ãªããŸãïŒ
Calling function: greet
Hello, Alice!
Finished calling function: greet
ããã¯ãã®ã³ã°ã远å ããã®ã«å®ç§ã«æ©èœããŸãã@simple_logger_decoratoræ§æã¯greet = simple_logger_decorator(greet)ã®ç³è¡£æ§æã§ããwrapper颿°ã¯å
ã®greet颿°ã®ååŸã«å®è¡ãããç®çã®å¯äœçšãéæããŸãã
åºæ¬çãªé¢æ°ã©ããã³ã°ã®åé¡ç¹
simple_logger_decoratorã¯äžå¿çãªä»çµã¿ã瀺ããŠããŸãããéå€§ãªæ¬ ç¹ããããŸããããã¯ãå
ã®é¢æ°ã®ã¡ã¿ããŒã¿ã倱ã£ãŠããŸãããšã§ããã¡ã¿ããŒã¿ãšã¯ã颿°åãdocstringãã¢ãããŒã·ã§ã³ãªã©ã颿°èªäœã«é¢ããæ
å ±ãæããŸãã
ãã³ã¬ãŒããããgreet颿°ã®ã¡ã¿ããŒã¿ã調ã¹ãŠã¿ãŸãããïŒ
print(f"Function name: {greet.__name__}")
print(f"Docstring: {greet.__doc__}")
@simple_logger_decoratorãé©çšããåŸã«ãã®ã³ãŒããå®è¡ãããšã次ã®ããã«ãªããŸãïŒ
Function name: wrapper
Docstring: None
ã芧ã®ãšããã颿°åã¯'wrapper'ã«ãªããdocstringã¯Noneã«ãªããŸãããããã¯ããã³ã¬ãŒã¿ãŒãwrapper颿°ãè¿ããPythonã®ã€ã³ããã¹ãã¯ã·ã§ã³ããŒã«ããå
ã®greet颿°ã§ã¯ãªããwrapper颿°ãå®éã®ãã³ã¬ãŒãããã颿°ãšããŠèªèããããã§ãã
ãªãã¡ã¿ããŒã¿ã®ä¿æãéèŠãªã®ã
颿°ã®ã¡ã¿ããŒã¿ã倱ããšãç¹ã«å€§èŠæš¡ãªãããžã§ã¯ãã倿§ãªããŒã ã«ãããŠãããã€ãã®åé¡ãåŒãèµ·ããå¯èœæ§ããããŸãïŒ
- ãããã°ã®å°é£ãïŒãããã°äžã«ã¹ã¿ãã¯ãã¬ãŒã¹ã§èª€ã£ã颿°åã衚瀺ããããšãéåžžã«æ··ä¹±ãæããŸãããšã©ãŒã®æ£ç¢ºãªå Žæãç¹å®ããã®ãé£ãããªããŸãã
- ã€ã³ããã¹ãã¯ã·ã§ã³ã®äœäžïŒããã¥ã¡ã³ããŒã·ã§ã³ãžã§ãã¬ãŒã¿ãŒïŒSphinxãªã©ïŒããªã³ã¿ãŒãIDEãªã©ã颿°ã®ã¡ã¿ããŒã¿ã«äŸåããããŒã«ã¯ããã³ã¬ãŒãããã颿°ã«é¢ããæ£ç¢ºãªæ å ±ãæäŸã§ããªããªããŸãã
- ãã¹ãã®åŠšãïŒãŠããããã¹ãã颿°åãdocstringã«é¢ããä»®å®ãç«ãŠãŠããå Žåã倱æããå¯èœæ§ããããŸãã
- ã³ãŒãã®å¯èªæ§ãšä¿å®æ§ïŒæç¢ºã§èª¬æçãªé¢æ°åãšdocstringã¯ãã³ãŒããçè§£ããããã«äžå¯æ¬ ã§ãããããã倱ããšãå ±åäœæ¥ãé·æçãªã¡ã³ããã³ã¹ã劚ããããŸãã
- ãã¬ãŒã ã¯ãŒã¯ãšã®äºææ§ïŒå€ãã®Pythonãã¬ãŒã ã¯ãŒã¯ãã©ã€ãã©ãªã¯ãç¹å®ã®ã¡ã¿ããŒã¿ãååšããããšãæåŸ ããŠããŸãããã®ã¡ã¿ããŒã¿ã倱ããããšãäºæãã¬åäœãå®å šãªå€±æã«ã€ãªããå¯èœæ§ããããŸãã
è€éãªã¢ããªã±ãŒã·ã§ã³ã«åãçµãã§ããã°ããŒãã«ãªãœãããŠã§ã¢éçºããŒã ãèããŠã¿ãŠãã ããããã³ã¬ãŒã¿ãŒãéèŠãªé¢æ°åã説æãåé€ããŠããŸããšãç°ãªãæåçã»èšèªçèæ¯ãæã€éçºè ãã³ãŒãããŒã¹ãè§£éããã®ã«èŠåŽãã誀解ããšã©ãŒã«ã€ãªããå¯èœæ§ããããŸããæç¢ºã«ä¿æãããã¡ã¿ããŒã¿ã¯ãå Žæãç¹å®ã®ã¢ãžã¥ãŒã«ã«é¢ããäºåã®çµéšã«é¢ä¿ãªããã³ãŒãã®æå³ã誰ã«ãšã£ãŠãæããã§ããããšãä¿èšŒããŸãã
functools.wrapsã«ããã¡ã¿ããŒã¿ã®ä¿æ
幞ããªããšã«ãPythonã®æšæºã©ã€ãã©ãªã«ã¯ãã®åé¡ã«å¯Ÿããçµã¿èŸŒã¿ã®è§£æ±ºçãfunctools.wrapsãã³ã¬ãŒã¿ãŒãçšæãããŠããŸãããã®ãã³ã¬ãŒã¿ãŒã¯ãä»ã®ãã³ã¬ãŒã¿ãŒå
ã§äœ¿çšããããã³ã¬ãŒãããã颿°ã®ã¡ã¿ããŒã¿ãä¿æããããã«ç¹å¥ã«èšèšãããŠããŸãã
functools.wrapsã®ä»çµã¿
wrapper颿°ã«@functools.wraps(func)ãé©çšãããšãå
ã®é¢æ°ïŒfuncïŒã®ååãdocstringãã¢ãããŒã·ã§ã³ããã®ä»ã®éèŠãªå±æ§ãã©ãããŒé¢æ°ã«ã³ããŒãããŸããããã«ãããã©ãããŒé¢æ°ã¯å€éšããã¯å
ã®é¢æ°ã§ãããã®ããã«èŠããŸãã
simple_logger_decoratorãfunctools.wrapsã䜿çšããããã«ãªãã¡ã¯ã¿ãªã³ã°ããŠã¿ãŸãããïŒ
import functools
def preserved_logger_decorator(func):
@functools.wraps(func)
def wrapper(*args, **kwargs):
print(f"Calling function: {func.__name__}")
result = func(*args, **kwargs)
print(f"Finished calling function: {func.__name__}")
return result
return wrapper
@preserved_logger_decorator
def greet_with_preservation(name):
"""Greets a person by name."""
return f"Hello, {name}!"
print(greet_with_preservation("Bob"))
print(f"Function name: {greet_with_preservation.__name__}")
print(f"Docstring: {greet_with_preservation.__doc__}")
ã§ã¯ããã®æ¹åããããã³ã¬ãŒã¿ãŒãé©çšããåŸã®åºåã調ã¹ãŠã¿ãŸãããïŒ
Calling function: greet_with_preservation
Hello, Bob!
Finished calling function: greet_with_preservation
Function name: greet_with_preservation
Docstring: Greets a person by name.
ã芧ã®ãšããã颿°åãšdocstringã¯æ£ããä¿æãããŠããŸãïŒããã¯ãç§ãã¡ã®ãã³ã¬ãŒã¿ãŒããããããã§ãã·ã§ãã«ã§äœ¿ãããããã®ã«ãã倧ããªæ¹åã§ãã
å®è·µçãªå¿çšãšé«åºŠãªã·ããªãª
ãã³ã¬ãŒã¿ãŒãã¿ãŒã³ã¯ãç¹ã«ã¡ã¿ããŒã¿ä¿æã䌎ãå ŽåãPythonéçºã«ãããŠå¹ åºãå¿çšç¯å²ããããŸããã°ããŒãã«ãªéçºè ã³ãã¥ããã£ã«é¢é£ãããæ§ã ãªæèã§ã®ãã®æçšæ§ã匷調ããããã€ãã®å®è·µçãªäŸãæ¢ã£ãŠã¿ãŸãããã
1. ã¢ã¯ã»ã¹å¶åŸ¡ãšæš©é
Webãã¬ãŒã ã¯ãŒã¯ãAPIéçºã§ã¯ããŠãŒã¶ãŒã®ããŒã«ãæš©éã«åºã¥ããŠç¹å®ã®é¢æ°ãžã®ã¢ã¯ã»ã¹ãå¶éããå¿ èŠããã°ãã°ãããŸãããã³ã¬ãŒã¿ãŒã¯ãã®ããžãã¯ããããã«åŠçã§ããŸãã
import functools
def requires_admin_role(func):
@functools.wraps(func)
def wrapper(*args, **kwargs):
current_user = kwargs.get('user') # Assuming user info is passed as a keyword argument
if current_user and current_user.role == 'admin':
return func(*args, **kwargs)
else:
return "Access Denied: Administrator role required."
return wrapper
class User:
def __init__(self, name, role):
self.name = name
self.role = role
@requires_admin_role
def delete_user(user_id, user):
return f"User {user_id} deleted by {user.name}."
admin_user = User("GlobalAdmin", "admin")
regular_user = User("RegularUser", "user")
# Example calls with metadata preserved
print(delete_user(101, user=admin_user))
print(delete_user(102, user=regular_user))
# Introspection of the decorated function
print(f"Decorated function name: {delete_user.__name__}")
print(f"Decorated function docstring: {delete_user.__doc__}")
ã°ããŒãã«ãªæèïŒåæ£ã·ã¹ãã ãäžçäžã®ãŠãŒã¶ãŒã«ãµãŒãã¹ãæäŸãããã©ãããã©ãŒã ã§ã¯ãæ¿èªãããæ
åœè
ã®ã¿ãïŒãŠãŒã¶ãŒã¢ã«ãŠã³ãã®åé€ã®ãããªïŒæ©å¯æ§ã®é«ãæäœãå®è¡ã§ããããã«ããããšãæãéèŠã§ãã@functools.wrapsã䜿çšããããšã§ãããã¥ã¡ã³ããŒã·ã§ã³ããŒã«ãAPIããã¥ã¡ã³ããçæããéã«ã颿°åãšèª¬æãæ£ç¢ºã«ä¿ãããç°ãªãã¿ã€ã ãŸãŒã³ãæ§ã
ãªã¢ã¯ã»ã¹ã¬ãã«ãæã€éçºè
ãã·ã¹ãã ãçè§£ããçµ±åãããããªããŸãã
2. ããã©ãŒãã³ã¹ç£èŠãšã¿ã€ãã³ã°èšæž¬
颿°ã®å®è¡æéãæž¬å®ããããšã¯ãããã©ãŒãã³ã¹æé©åã«ãšã£ãŠéåžžã«éèŠã§ãããã³ã¬ãŒã¿ãŒã¯ãã®ããã»ã¹ãèªååã§ããŸãã
import functools
import time
def timing_decorator(func):
@functools.wraps(func)
def wrapper(*args, **kwargs):
start_time = time.time()
result = func(*args, **kwargs)
end_time = time.time()
print(f"Function '{func.__name__}' took {end_time - start_time:.4f} seconds to execute.")
return result
return wrapper
@timing_decorator
def complex_calculation(n):
"""Performs a computationally intensive task."""
time.sleep(1) # Simulate work
return sum(i*i for i in range(n))
result = complex_calculation(100000)
print(f"Calculation result: {result}")
print(f"Timing function name: {complex_calculation.__name__}")
print(f"Timing function docstring: {complex_calculation.__doc__}")
ã°ããŒãã«ãªæèïŒãããã¯ãŒã¯ã®é å»¶ããµãŒããŒã®è² è·ãç°ãªãå°åã«ããããŠãŒã¶ãŒã®ããã«ã³ãŒããæé©åããå Žåãæ£ç¢ºãªã¿ã€ãã³ã°èšæž¬ãäžå¯æ¬ ã§ãããã®ãããªãã³ã¬ãŒã¿ãŒã䜿çšãããšãéçºè ã¯äžå¿çãªããžãã¯ãä¹±éã«ããããšãªããããã©ãŒãã³ã¹ã®ããã«ããã¯ãç°¡åã«ç¹å®ã§ããŸããä¿æãããã¡ã¿ããŒã¿ã«ãããããã©ãŒãã³ã¹ã¬ããŒããæ£ãã颿°ã«æç¢ºã«åž°å±ããã忣ããŒã ã®ãšã³ãžãã¢ãåé¡ãå¹ççã«èšºæã»è§£æ±ºããã®ã«åœ¹ç«ã¡ãŸãã
3. çµæã®ãã£ãã·ã¥
èšç®ã³ã¹ããé«ããåãåŒæ°ã§ç¹°ãè¿ãåŒã³åºããã颿°ã«ã€ããŠã¯ããã£ãã·ã¥ãããã©ãŒãã³ã¹ã倧å¹
ã«åäžãããããšãã§ããŸããPythonã®functools.lru_cacheã¯ãã®ä»£è¡šäŸã§ãããç¹å®ã®ããŒãºã«åãããŠç¬èªã«æ§ç¯ããããšãã§ããŸãã
import functools
def simple_cache_decorator(func):
cache = {}
@functools.wraps(func)
def wrapper(*args, **kwargs):
# Create a cache key. For simplicity, only consider positional args.
# A real-world cache would need more sophisticated key generation,
# especially for kwargs and mutable types.
key = args
if key in cache:
print(f"Cache hit for '{func.__name__}' with args {args}")
return cache[key]
else:
print(f"Cache miss for '{func.__name__}' with args {args}")
result = func(*args, **kwargs)
cache[key] = result
return result
return wrapper
@simple_cache_decorator
def fibonacci(n):
"""Calculates the nth Fibonacci number recursively."""
if n < 2:
return n
return fibonacci(n - 1) + fibonacci(n - 2)
print(f"Fibonacci(10): {fibonacci(10)}")
print(f"Fibonacci(10) again: {fibonacci(10)}") # This should be a cache hit
print(f"Fibonacci function name: {fibonacci.__name__}")
print(f"Fibonacci function docstring: {fibonacci.__doc__}")
ã°ããŒãã«ãªæèïŒç°ãªã倧éžã®ãŠãŒã¶ãŒã«ããŒã¿ãäŸçµŠããå¯èœæ§ã®ããã°ããŒãã«ã¢ããªã±ãŒã·ã§ã³ã§ã¯ãé »ç¹ã«ãªã¯ãšã¹ãããããèšç®ã³ã¹ãã®é«ãçµæããã£ãã·ã¥ããããšã§ããµãŒããŒã®è² è·ãšå¿çæéãåçã«åæžã§ããŸããããŒã¿åæãã©ãããã©ãŒã ãæ³åããŠã¿ãŠãã ãããè€éãªã¯ãšãªçµæããã£ãã·ã¥ããããšã§ãäžçäžã®ãŠãŒã¶ãŒãžã®ã€ã³ãµã€ãã®æäŸãé«éåãããŸãããã³ã¬ãŒãããããã£ãã·ã¥é¢æ°ã®ä¿æãããã¡ã¿ããŒã¿ã¯ãã©ã®èšç®ããªããã£ãã·ã¥ãããŠããã®ããçè§£ããã®ã«åœ¹ç«ã¡ãŸãã
4. å ¥åæ€èšŒ
颿°ã®å ¥åãç¹å®ã®åºæºãæºãããŠããããšãä¿èšŒããã®ã¯ãäžè¬çãªèŠä»¶ã§ãããã³ã¬ãŒã¿ãŒã¯ãã®æ€èšŒããžãã¯ãäžå åã§ããŸãã
import functools
def validate_positive_integer(param_name):
def decorator(func):
@functools.wraps(func)
def wrapper(*args, **kwargs):
param_index = -1
try:
# Find the index of the parameter by name for positional arguments
param_index = func.__code__.co_varnames.index(param_name)
if param_index < len(args):
value = args[param_index]
if not isinstance(value, int) or value <= 0:
raise ValueError(f"'{param_name}' must be a positive integer.")
except ValueError:
# If not found as positional, check keyword arguments
if param_name in kwargs:
value = kwargs[param_name]
if not isinstance(value, int) or value <= 0:
raise ValueError(f"'{param_name}' must be a positive integer.")
else:
# Parameter not found, or it's optional and not provided
# Depending on requirements, you might want to raise an error here too
pass
return func(*args, **kwargs)
return wrapper
return decorator
@validate_positive_integer('count')
def process_items(items, count):
"""Processes a list of items a specified number of times."""
print(f"Processing {len(items)} items, {count} times.")
return len(items) * count
print(process_items(['a', 'b'], count=5))
try:
process_items(['c'], count=-2)
except ValueError as e:
print(e)
try:
process_items(['d'], count='three')
except ValueError as e:
print(e)
print(f"Validation function name: {process_items.__name__}")
print(f"Validation function docstring: {process_items.__doc__}")
ã°ããŒãã«ãªæèïŒåœéçãªããŒã¿ã»ããããŠãŒã¶ãŒå ¥åãæ±ãã¢ããªã±ãŒã·ã§ã³ã§ã¯ãå ç¢ãªæ€èšŒãäžå¯æ¬ ã§ããããšãã°ãæ°éãäŸ¡æ Œãæž¬å®å€ãªã©ã®æ°å€å ¥åãæ€èšŒããããšã§ãç°ãªãããŒã«ã©ã€ãŒãŒã·ã§ã³èšå®éã§ã®ããŒã¿æŽåæ§ãä¿èšŒãããŸããã¡ã¿ããŒã¿ãä¿æããããã³ã¬ãŒã¿ãŒã䜿çšãããšã颿°ã®ç®çãšæåŸ ãããåŒæ°ãåžžã«æç¢ºã«ãªããäžçäžã®éçºè ãæ€èšŒæžã¿é¢æ°ã«ããŒã¿ãæ£ããæž¡ãããããªããããŒã¿åãç¯å²ã®äžäžèŽã«é¢é£ããäžè¬çãªãšã©ãŒãé²ãããšãã§ããŸãã
åŒæ°ãæã€ãã³ã¬ãŒã¿ãŒã®äœæ
æã«ã¯ãç¬èªã®åŒæ°ã§èšå®ã§ãããã³ã¬ãŒã¿ãŒãå¿ èŠã«ãªãããšããããŸããããã¯ã颿°ãããã«äžå±€ãã¹ããããããšã§å®çŸãããŸãã
import functools
def repeat(num_times):
def decorator_repeat(func):
@functools.wraps(func)
def wrapper(*args, **kwargs):
for _ in range(num_times):
result = func(*args, **kwargs)
return result
return wrapper
return decorator_repeat
@repeat(num_times=3)
def say_hello(name):
"""Prints a greeting."""
print(f"Hello, {name}!")
say_hello("World")
print(f"Repeat function name: {say_hello.__name__}")
print(f"Repeat function docstring: {say_hello.__doc__}")
ãã®ãã¿ãŒã³ã«ãããç¹å®ã®ããŒãºã«åãããŠã«ã¹ã¿ãã€ãºã§ããéåžžã«æè»ãªãã³ã¬ãŒã¿ãŒãå¯èœã«ãªããŸãã@repeat(num_times=3)æ§æã¯say_hello = repeat(num_times=3)(say_hello)ã®ç³è¡£æ§æã§ããå€åŽã®é¢æ°repeatããã³ã¬ãŒã¿ãŒã®åŒæ°ãåãåããå®éã®ãã³ã¬ãŒã¿ãŒïŒdecorator_repeatïŒãè¿ããŸãããããŠããããã¡ã¿ããŒã¿ãä¿æãããŸãŸããžãã¯ãé©çšããŸãã
ãã³ã¬ãŒã¿ãŒå®è£ ã®ãã¹ããã©ã¯ãã£ã¹
ãã³ã¬ãŒã¿ãŒãé©åã«åäœããä¿å®å¯èœã§ãã°ããŒãã«ãªãªãŒãã£ãšã³ã¹ã«çè§£ãããããã«ããããã«ã¯ã以äžã®ãã¹ããã©ã¯ãã£ã¹ã«åŸã£ãŠãã ããïŒ
- åžžã«
@functools.wraps(func)ã䜿çšããïŒããã¯ã¡ã¿ããŒã¿ã®æå€±ãé¿ããããã®æãéèŠãªå®è·µã§ããããã«ãããã€ã³ããã¹ãã¯ã·ã§ã³ããŒã«ãä»ã®éçºè ããã³ã¬ãŒãããã颿°ãæ£ç¢ºã«çè§£ã§ããããã«ãªããŸãã - äœçœ®åŒæ°ãšããŒã¯ãŒãåŒæ°ãæ£ããæ±ãïŒã©ãããŒé¢æ°ã§
*argsãš**kwargsã䜿çšããŠããã³ã¬ãŒãããã颿°ãåãåãå¯èœæ§ã®ããä»»æã®åŒæ°ãåãå ¥ããŸãã - ãã³ã¬ãŒãããã颿°ã®çµæãè¿ãïŒã©ãããŒé¢æ°ããå ã®ãã³ã¬ãŒãããã颿°ããè¿ãããå€ãè¿ãããã«ããŠãã ããã
- ãã³ã¬ãŒã¿ãŒã®çŠç¹ãçµãïŒåãã³ã¬ãŒã¿ãŒã¯çæ³çã«ã¯ãåäžã®æç¢ºã«å®çŸ©ãããã¿ã¹ã¯ïŒäŸïŒãã®ã³ã°ãã¿ã€ãã³ã°èšæž¬ãèªèšŒïŒãå®è¡ãã¹ãã§ããè€æ°ã®ãã³ã¬ãŒã¿ãŒãæ§æããããšã¯å¯èœã§ããããã°ãã°æãŸããã§ãããåã ã®ãã³ã¬ãŒã¿ãŒã¯ã·ã³ãã«ã§ããã¹ãã§ãã
- ãã³ã¬ãŒã¿ãŒãææžåããïŒãã³ã¬ãŒã¿ãŒãäœããããããã®åŒæ°ïŒããããã°ïŒãããã³å¯äœçšã«ã€ããŠèª¬æããæç¢ºãªdocstringãèšè¿°ããŠãã ãããããã¯äžçäžã®éçºè ã«ãšã£ãŠéåžžã«éèŠã§ãã
- ãã³ã¬ãŒã¿ãŒãžã®åŒæ°æž¡ããæ€èšããïŒãã³ã¬ãŒã¿ãŒã«èšå®ãå¿
èŠãªå Žåã¯ã
repeatã®äŸã§ç€ºãããããªãã¹ãããããã³ã¬ãŒã¿ãŒãã¿ãŒã³ïŒãã³ã¬ãŒã¿ãŒãã¡ã¯ããªïŒã䜿çšããŸãã - ãã³ã¬ãŒã¿ãŒã培åºçã«ãã¹ãããïŒãã³ã¬ãŒã¿ãŒã®ãŠããããã¹ããèšè¿°ããæ§ã ãªé¢æ°ã·ã°ããã£ã§æ£ããåäœããã¡ã¿ããŒã¿ãä¿æãããããšã確èªããŠãã ããã
- ãã³ã¬ãŒã¿ãŒã®é åºã«æ³šæããïŒè€æ°ã®ãã³ã¬ãŒã¿ãŒãé©çšããå Žåããã®é åºãéèŠã§ãã颿°å®çŸ©ã«æãè¿ããã³ã¬ãŒã¿ãŒãæåã«é©çšãããŸããããã¯ãããããã©ã®ããã«çžäºäœçšããã¡ã¿ããŒã¿ãã©ã®ããã«é©çšããããã«åœ±é¿ããŸããããšãã°ãã«ã¹ã¿ã ãã³ã¬ãŒã¿ãŒãæ§æããŠããå Žåã
@functools.wrapsã¯æãå åŽã®ã©ãããŒé¢æ°ã«é©çšããå¿ èŠããããŸãã
ãã³ã¬ãŒã¿ãŒå®è£ ã®æ¯èŒ
èŠçŽãããšã2ã€ã®ã¢ãããŒãã®çŽæ¥çãªæ¯èŒã¯æ¬¡ã®ãšããã§ãïŒ
颿°ã©ããã³ã°ïŒåºæ¬ïŒ
- é·æïŒæ©èœã®è¿ éãªè¿œå ã®ããã«å®è£ ãç°¡åã§ãã
- çæïŒå ã®é¢æ°ã®ã¡ã¿ããŒã¿ïŒååãdocstringãªã©ïŒãç Žå£ãããããã°ã®åé¡ãäžååãªã€ã³ããã¹ãã¯ã·ã§ã³ãä¿å®æ§ã®äœäžã«ã€ãªãããŸãã
- 䜿çšäŸïŒã¡ã¿ããŒã¿ãåé¡ã«ãªããªããéåžžã«ã·ã³ãã«ã§äœ¿ãæšãŠã®ãã³ã¬ãŒã¿ãŒïŒãã£ãã«æšå¥šãããŸããïŒã
ã¡ã¿ããŒã¿ä¿æïŒfunctools.wrapsã䜿çšïŒ
- é·æïŒå ã®é¢æ°ã®ã¡ã¿ããŒã¿ãä¿æããæ£ç¢ºãªã€ã³ããã¹ãã¯ã·ã§ã³ãç°¡åãªãããã°ãããè¯ãããã¥ã¡ã³ããŒã·ã§ã³ãããã³æ¹åãããä¿å®æ§ãä¿èšŒããŸããã°ããŒãã«ããŒã ã®ããã«ã³ãŒãã®æç¢ºããšå ç¢æ§ãä¿é²ããŸãã
- çæïŒ
@functools.wrapsãå«ããããããããã«åé·ã«ãªããŸãã - 䜿çšäŸïŒæ¬çªã³ãŒãã«ãããã»ãšãã©ãã¹ãŠã®ãã³ã¬ãŒã¿ãŒå®è£ ãç¹ã«å ±æãããžã§ã¯ãããªãŒãã³ãœãŒã¹ãããžã§ã¯ãããŸãã¯ãã¬ãŒã ã¯ãŒã¯ã䜿çšããå Žåãããã¯ããããã§ãã·ã§ãã«ãªPythonéçºã®ããã®æšæºçãã€æšå¥šãããã¢ãããŒãã§ãã
çµè«
Pythonã®ãã³ã¬ãŒã¿ãŒãã¿ãŒã³ã¯ãã³ãŒãã®æ©èœæ§ãšæ§é ã匷åããããã®åŒ·åãªããŒã«ã§ããåºæ¬çãªé¢æ°ã©ããã³ã°ã¯åçŽãªæ¡åŒµãéæã§ããŸãããããã¯éèŠãªé¢æ°ã®ã¡ã¿ããŒã¿ã倱ããšãã倧ããªä»£åã䌎ããŸãããããã§ãã·ã§ãã«ã§ãä¿å®å¯èœã§ãã°ããŒãã«ã«ååããŠè¡ããœãããŠã§ã¢éçºã®ããã«ã¯ãfunctools.wrapsã䜿çšããã¡ã¿ããŒã¿ä¿æã¯ãåãªããã¹ããã©ã¯ãã£ã¹ã§ã¯ãªããäžå¯æ¬ ã§ãã
@functools.wrapsãäžè²«ããŠé©çšããããšã§ãéçºè
ã¯ãã³ã¬ãŒãããã颿°ãã€ã³ããã¹ãã¯ã·ã§ã³ããããã°ãããã¥ã¡ã³ããŒã·ã§ã³ã«é¢ããŠæåŸ
ã©ããã«åäœããããšãä¿èšŒããŸããããã«ãããããã¯ãªãŒã³ã§ãããå
ç¢ã§ãããçè§£ããããã³ãŒãããŒã¹ãçãŸããããã¯ç°ãªãå°ççãªå Žæãã¿ã€ã ãŸãŒã³ãæåçèæ¯ãè¶ããŠäœæ¥ããããŒã ã«ãšã£ãŠäžå¯æ¬ ã§ãããã®å®è·µãåãå
¥ããŠãã°ããŒãã«ãªãªãŒãã£ãšã³ã¹ã®ããã®ããè¯ãPythonã¢ããªã±ãŒã·ã§ã³ãæ§ç¯ããŸãããã